package com.xb.loan.util.binaryConvert.parse.list;


import com.xb.loan.util.binaryConvert.ConvertUtil;
import com.xb.loan.util.binaryConvert.config.ParseConfig;
import com.xb.loan.util.binaryConvert.config.ParseConfigManager;
import com.xb.loan.util.binaryConvert.exception.ParseException;
import com.xb.loan.util.binaryConvert.parse.ParseAble;
import com.xb.loan.util.binaryConvert.parse.ParsePointer;

import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;

/**
 * //TODO 暂时不支持数组的转换，不支持和map的嵌套
 *
 * 
 */
@SuppressWarnings("unchecked")
public class ListParser implements ParseAble<List> {

	@Override
	public List convert(byte[] src, ParsePointer pointer, Class<?> clazz,
                        ParseConfig config) throws ParseException {
		// 递归调用
		List<Object> objs = (List<Object>) convert(src, pointer, config, 1);

		return objs;
	}

	private Object convert(byte[] src, ParsePointer pointer,
			ParseConfig config, int deep) {

		int sizes = ConvertUtil.readSizes(src, pointer);

		if (sizes == 0) {

			return null;
		}

		List<Object> objs = new ArrayList<Object>(sizes);

		for (int i = 0; i < sizes; i++) {

			Object obj = null;

			if (deep == config.getListDeep()) {

				ParseAble parser = ParseConfigManager.getParser(ParseConfigManager.getParseClassType(config.getValueClass()));

				obj = parser.convert(src, pointer, config.getValueClass(), config);
			} else {

				obj = convert(src, pointer, config, deep + 1);
			}

			objs.add(obj);
		}

		return objs;
	}

	@Override
	/*
	 * * config: list的配置信息
	 */
	public byte[] format(List obj, ParseConfig config) throws ParseException {

		if (obj == null) {

			return new byte[] { 0 };
		}

		List<byte[]> elementBytes = new LinkedList<byte[]>();
		// 总共字节长度
		int sizes = 0;

		byte[] bb = null;

		try {
			// 递归调用
			bb = format(obj, config, 1);
			
		} catch (Exception e) {

			throw new ParseException("ListParser parse " + obj + " error.", e);
		}

		sizes += bb.length;

		elementBytes.add(bb);

		return ConvertUtil.combatAll(elementBytes, sizes);
	}

	private byte[] format(List obj, ParseConfig config, int deep)
			throws ParseException {
		
		// 添加list属性长度
		List<byte[]> elementBytes = new LinkedList<byte[]>();

		byte[] sizeData = ConvertUtil.convertSizes(obj.size());
		elementBytes.add(sizeData);
		// 总共字节长度
		int sizes = sizeData.length;

		for (int i = 0; i < obj.size(); i++) {

			byte[] data = null;
			// 如果不是list,递归结束
			if(deep == config.getListDeep()){
				// 获取解析的parser
				ParseAble parser = ParseConfigManager
						.getParser(ParseConfigManager.getParseClassType(config.getValueClass()));

				data = parser.format(obj.get(i), null);
			} else{
				
				data = format((List) obj.get(i), config, deep + 1);
			}

			sizes += data.length;

			elementBytes.add(data);
		}

		return ConvertUtil.combatAll(elementBytes, sizes);
	}

}
